package com.ccp.dev.workflow.controller;

import com.ccp.dev.core.basic.annotion.Action;
import com.ccp.dev.core.basic.annotion.ActionExecOrder;
import com.ccp.dev.core.basic.consts.UrlConstants;
import com.ccp.dev.core.basic.internationalization.SysBaseController;
import com.ccp.dev.core.basic.model.SysAuditModelType;
import com.ccp.dev.core.basic.response.ResultData;
import com.ccp.dev.core.basic.util.ContextUtil;
import com.ccp.dev.core.basic.util.UUIDUtils;
import com.ccp.dev.core.basic.web.query.QueryFilter;
import com.ccp.dev.core.jms.IMessageHandler;
import com.ccp.dev.core.util.BeanUtils;
import com.ccp.dev.core.util.RequestUtil;
import com.ccp.dev.core.util.StringUtil;
import com.ccp.dev.core.util.log.SysAuditThreadLocalHolder;
import com.ccp.dev.system.model.SysUser;
import com.ccp.dev.system.service.SysOrgService;
import com.ccp.dev.system.service.SysUserService;
import com.ccp.dev.workflow.bpmutil.ServiceUtil;
import com.ccp.dev.workflow.model.BpmTaskExe;
import com.ccp.dev.workflow.model.ProcessRun;
import com.ccp.dev.workflow.model.bpm.BpmRunLog;
import com.ccp.dev.workflow.service.*;
import com.ccp.dev.workflow.service.bpm.BpmRunLogService;
import com.ccp.dev.workflow.service.bpm.thread.MessageUtil;
import org.apache.commons.lang.StringUtils;
import org.flowable.task.service.impl.persistence.entity.TaskEntity;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletRequest;
import java.util.Date;
import java.util.List;
import java.util.Map;

/**
 * ClassDescribe 任务转办代理 控制器类
 * @author: fanruiqi
 * Date: 2019-08-29
 * Since:1
 * To change this template use File | Settings | File Templates.
 */
@Controller
@RequestMapping(UrlConstants.PROJECT_ROOT +UrlConstants.PROJECT_MODULE_WORKFLOW+"/bpmTaskExe")
public class BpmTaskExeController  extends SysBaseController {
    private static final Logger logger = LoggerFactory.getLogger(BpmTaskExeService.class);

    @Resource
    private BpmTaskExeService bpmTaskExeService;
    @Resource
    private BpmService bpmService;
    @Resource
    private ProcessRunService processRunService;
    @Resource
    private ActDefModelService actDefModelService;
    @Resource
    private SysUserService sysUserService;
    @Resource
    private SysOrgService sysOrgService;
    @Resource
    private BpmRunLogService bpmRunLogService;
    @Resource
    private TaskUserService taskUserService;

    /**
     * 保存转交代办任务
     * @param request
     * @return
     */
    @RequestMapping("/assignSave")
    @Action(description = "转交代办保存处理",ownermodel = SysAuditModelType.PROCESS_CENTER,
        detail = "添加转办代理任务<#if success>成功<#else>失败</#if>")
    @ResponseBody
    public ResultData assignSave(HttpServletRequest request){
        String assigneeId = RequestUtil.getString(request, "assigneeId");
        if(StringUtil.isEmpty(assigneeId)){
            return getResultDataError("bpmTaskExe.newUser.failure");
        }
        String taskId = RequestUtil.getString(request,"taskId");
        String assigneeName = RequestUtil.getString(request, "assigneeName");
        String memo = RequestUtil.getString(request, "memo");
        String informType = RequestUtil.getStringAry(request, "informType");
        try{
            TaskEntity taskEntity = bpmService.getTask(taskId);
            if(BeanUtils.isEmpty(taskEntity)){
                return getResultDataError("bpmTaskExe.over.failure");
            }
            //原任务执行人
            String assignee = taskEntity.getAssignee();
            //任务人不为空且和当前用户不同
            SysUser sysUser = (SysUser) ContextUtil.getCurrentUser();
            if(sysUser.getUserId().equals(assigneeId)){
                return getResultDataError("bpmTaskExe.executive.failure");//不能转办给任务执行人！
            }
            if( ServiceUtil.isAssigneeNotEmpty(assignee) &&  assignee.equals(assigneeId)){
                return getResultDataError("bpmTaskExe.executive.failure");//不能转办给任务执行人！
            }
            if(ServiceUtil.isAssigneeNotEmpty(assignee)){
                if(!assignee.equals(sysUser.getUserId())) {
                    return getResultDataError("bpmTaskExe.user.failure");//对不起，转办失败。您（已）不是任务的执行人！
                }
            }
            ProcessRun processRun = processRunService.getByProcInstanceId(taskEntity.getProcessInstanceId());
            String procDefId = processRun.getProcDefId();
            boolean rtn = actDefModelService.allowDivert(procDefId);
            if(!rtn){
                return getResultDataError("bpmTaskExe.assign.failure");
            }


            BpmTaskExe bpmTaskExe = new BpmTaskExe();
            bpmTaskExe.setId(UUIDUtils.getUUIDFor32());
            bpmTaskExe.setTaskId(taskId);
            bpmTaskExe.setAssigneeId(assigneeId);
            bpmTaskExe.setAssigneeName(assigneeName);
            bpmTaskExe.setOwnerId(sysUser.getUserId());
            bpmTaskExe.setOwnerName(sysUser.getFullName());
            bpmTaskExe.setSubject(processRun.getSubject());
            bpmTaskExe.setStatus(BpmTaskExe.STATUS_INIT);
            bpmTaskExe.setMemo(memo);
            bpmTaskExe.setCreateTime(new Date());
            bpmTaskExe.setProcInstId(taskEntity.getProcessInstanceId());
            bpmTaskExe.setTaskDefKey(taskEntity.getTaskDefinitionKey());
            bpmTaskExe.setTaskName(taskEntity.getName());
            bpmTaskExe.setAssignType(BpmTaskExe.TYPE_TRANSMIT);
            bpmTaskExe.setRunId(processRun.getRunId());
            bpmTaskExe.setTypeId(processRun.getTypeId());
            bpmTaskExe.setInformType(informType);
            String orgId = ContextUtil.getCurrentOrgId();
            String tenId = sysOrgService.getTenIdByOrgId(orgId);
            bpmTaskExe.setTenantId(tenId);
            bpmTaskExeService.assignSave(bpmTaskExe);
            SysAuditThreadLocalHolder.putParamerter("success",true);
            return getResultDataSuccess("bpmTaskExe.success");
        }catch (Exception e){
            logger.error(e.getMessage());
            SysAuditThreadLocalHolder.putParamerter("success",false);
            return getResultDataError("bpmTaskExe.failure",1,e.getMessage());
        }
    }

    /**
     * 跳转转办代理实例页面
     * @return
     */
    @RequestMapping(UrlConstants.VIEW_DISPATCH_PREFIX+UrlConstants.MODULE_FUNCTION_LIST)
    @Action(description = "转办代理实例页面",exectype = "页面跳转日志",ownermodel=SysAuditModelType.PROCESS_MANAGEMENT)
    public String viewList(Model model){
        SysUser user = (SysUser) ContextUtil.getCurrentUser();
        model.addAttribute("privacyLevel", user.getPrivacyLevel());
        return getAutoView();
    }

    /**
     * 查询转办代理实例页面列表数据
     * @param request
     * @return
     */
    @RequestMapping(UrlConstants.MODULE_FUNCTION_LIST)
    @Action(description = "转办代理实例列表数据查询",ownermodel = SysAuditModelType.PROCESS_MANAGEMENT
            ,detail = "<#if success>转办代理实例列表数据查询成功</#if>")
    @ResponseBody
    public ResultData queryList(HttpServletRequest request){
        boolean isAdmin = ContextUtil.isSuperAdmin();
        List<BpmTaskExe> list = null;
        QueryFilter queryFilter = new QueryFilter(request,true);
        String nodePath = RequestUtil.getString(request, "nodePath");
        if(StringUtils.isNotEmpty(nodePath)) {
            queryFilter.addFilter("nodePath", nodePath + "%");
        }
        queryFilter.addFilter("exceptDefStatus", 3);
        if(isAdmin){
            list = bpmTaskExeService.queryList(queryFilter);
        }else{
            String orgId = ContextUtil.getCurrentOrgId();
            String tenId = sysOrgService.getTenIdByOrgId(orgId);
            queryFilter.addFilter("tenantId", tenId);
            list = bpmTaskExeService.queryList(queryFilter);
        }
        SysAuditThreadLocalHolder.putParamerter("success",true);
        return getResultDataSuccess("query.success",queryFilter.getPageBean().getTotalCount(),list);
    }

    /**
     * 跳转转发代理事宜页面
     * @return
     */
    @RequestMapping(UrlConstants.VIEW_DISPATCH_PREFIX+"/taskExeList")
    @Action(description = "转发代理事宜页面跳转成功",exectype = "页面跳转日志",ownermodel = SysAuditModelType.PROCESS_CENTER)
    public String viewTaskExeList(){ return getAutoView(); }

    /**
     * 获取转发代理事宜列表数据
     * @param request
     * @return
     */
    @RequestMapping("/taskExeList")
    @Action(description = "转发代理事宜列表数据查询",ownermodel = SysAuditModelType.PROCESS_CENTER,detail = "转发代理事宜列表数据查询<#if success>成功<#else>失败</#if>")
    @ResponseBody
    public ResultData queryTaskExeList(HttpServletRequest request){
        QueryFilter queryFilter = new QueryFilter(request);
        String userId = ContextUtil.getCurrentUserId();
        queryFilter.addFilter("ownerId",userId);
        String nodePath = RequestUtil.getString(request,"nodePath");
        if(StringUtil.isNotEmpty(nodePath)){
            queryFilter.addFilter("nodePath",nodePath+"%");
        }
        try {
            List<BpmTaskExe> list = bpmTaskExeService.queryList(queryFilter);
            SysAuditThreadLocalHolder.putParamerter("success",true);
            return getResultDataSuccess("query.success", queryFilter.getPageBean().getTotalCount(), list);
        }catch (Exception e){
            logger.error(e.getMessage());
            SysAuditThreadLocalHolder.putParamerter("success",false);
            return getResultDataError("query.failure");
        }
    }

    /**
     *转发代理事宜-明细页面
     * @return
     */
    @RequestMapping(UrlConstants.VIEW_DISPATCH_PREFIX+UrlConstants.MODULE_FUNCTION_GET)
    @Action(description = "转发代理事宜明细页面",exectype = "页面跳转日志",ownermodel = SysAuditModelType.PROCESS_CENTER
        ,detail="<#if success>转发代理事宜明细页面数据查询成功</#if>")
    public String windowGet(HttpServletRequest request,Model model){
        String id = RequestUtil.getString(request,"id");
        BpmTaskExe bpmTaskExe = bpmTaskExeService.getOneById(id);
        if(bpmTaskExe!=null) {
            model.addAttribute("exe",bpmTaskExe);
            SysAuditThreadLocalHolder.putParamerter("success",true);
        }
        return getAutoView();
    }

    /**
     *转发代理事宜-删除任务转发代理
     * @param request
     * @return
     */
    @RequestMapping(UrlConstants.MODULE_FUNCTION_DELETE)
    @Action(description = "删除任务转发代理",execOrder = ActionExecOrder.BEFORE,ownermodel = SysAuditModelType.PROCESS_MANAGEMENT,detail = "转发代理任务删除<#if success>成功<#else>失败</#if>")
    @ResponseBody
    public ResultData del(HttpServletRequest request){
        try {
            String id = RequestUtil.getString(request, "id");
            bpmTaskExeService.delById(id);
            SysAuditThreadLocalHolder.putParamerter("success",true);
            return getResultDataSuccess("bpmTaskExe.delete.success");
        }catch (Exception e){
            logger.error(e.getMessage());
            SysAuditThreadLocalHolder.putParamerter("success",false);
            return getResultDataError("bpmTaskExe.delete.failure",1,e.getMessage());
        }
    }
    /**
     *转发代理事宜-取消弹窗
     * @param model
     * @return
     */
    @RequestMapping(UrlConstants.VIEW_DISPATCH_PREFIX+"/delBatchOnlyOne")
    @Action(description = "转办代理取消页面弹窗",exectype = "页面跳转日志",ownermodel = SysAuditModelType.PROCESS_MANAGEMENT)
    public String windowDelBatch(HttpServletRequest request,Model model){
        String id = RequestUtil.getString(request,"id");
        Map<String, IMessageHandler> handlersMap=ServiceUtil.getHandlerMap();
        model.addAttribute("id",id);
        if(!handlersMap.isEmpty()){
            model.addAttribute("handlersMap",handlersMap);
        }
        return getAutoView();
    }
    /**
     *转发代理事宜-批量取消弹窗
     * @param model
     * @return
     */
    @RequestMapping(UrlConstants.VIEW_DISPATCH_PREFIX+UrlConstants.MODULE_FUNCTION_DELETE_BATCH)
    @Action(description = "转办代理批量取消页面弹窗",exectype = "页面跳转日志",ownermodel = SysAuditModelType.PROCESS_MANAGEMENT)
    public String windowDelBatchs(HttpServletRequest request,Model model){
        String ids = RequestUtil.getString(request,"ids");
        Map<String, IMessageHandler> handlersMap=ServiceUtil.getHandlerMap();
        model.addAttribute("ids",ids);
        if(!handlersMap.isEmpty()){
            model.addAttribute("handlersMap",handlersMap);
        }
        return getAutoView();
    }

    /**
     *转发代理事宜-取消
     * @param request
     * @return
     */
    @RequestMapping("/delBatchOnlyOne")
    @Action(description = "取消任务转办代理",ownermodel = SysAuditModelType.PROCESS_MANAGEMENT,detail = "转发代理任务取消<#if success>成功<#else>失败</#if>")
    @ResponseBody
    public ResultData cancelOne(HttpServletRequest request){
        String id = RequestUtil.getString(request,"id");
        String opinion   = RequestUtil.getString(request,"opinion");
        String informType= RequestUtil.getString(request,"informType");

        String bpmTaskExeType = null;
        try {
            BpmTaskExe bpmTaskExe = bpmTaskExeService.getOneById(id);
            if(BpmTaskExe.TYPE_ASSIGNEE.equals(bpmTaskExe.getAssignType())){
                bpmTaskExeType="代理";
            }else if(BpmTaskExe.TYPE_TRANSMIT.equals(bpmTaskExe.getAssignType())){
                bpmTaskExeType="转办";
            }
            String taskId = bpmTaskExe.getTaskId();
            TaskEntity taskEntity = bpmService.getTask(taskId);
            if(taskEntity==null){
                bpmTaskExeService.cancelOver(id);
                return getResultDataError("bpmTaskExe.task.over");
            }
            String ownerId = bpmTaskExe.getOwnerId();
            if(ownerId==null){
                return getResultDataError("bpmTaskExe.oldUser.failure");
            }
            SysUser sysUser = sysUserService.getOneById(ownerId);
            if(sysUser==null){
                return getResultDataError("bpmTaskExe.oldUser.failure");
            }
            //取消转发/代理
            bpmTaskExeService.cancelBacth(bpmTaskExe, sysUser, opinion, informType);
            //记录日志
            ProcessRun processRun = processRunService.getByProcInstanceId(bpmTaskExe.getProcInstId());
            String memo = "流程:" + processRun.getSubject() + ", 【" + sysUser.getFullName() + "】将转办任务【" + bpmTaskExe.getSubject()+ "】 取消";
            bpmRunLogService.addRunLog(processRun.getRunId(), BpmRunLog.OPERATOR_TYPE_BACK, memo);
            //添加操作日志
            SysAuditThreadLocalHolder.putParamerter("success",true);
            return getResultDataSuccess("bpmTaskExe.cancel.success");
        }catch (Exception e){
            logger.error(e.getMessage());
            SysAuditThreadLocalHolder.putParamerter("success",false);
            return getResultDataError("bpmTaskExe.cancel.failure");
        }
    }
    /**
     *转发代理事宜-批量取消
     * @param request
     * @return
     */
    @RequestMapping(UrlConstants.MODULE_FUNCTION_DELETE_BATCH)
    @Action(description = "批量取消任务转办代理",ownermodel = SysAuditModelType.PROCESS_MANAGEMENT,detail = "转发代理任务批量取消<#if success>全部成功<#elseif some>部分成功<#else>失败</#if>")
    @ResponseBody
    public ResultData cancelBatch(HttpServletRequest request){
        String ids = RequestUtil.getString(request,"ids");
        String opinion   = RequestUtil.getString(request,"opinion");
        String informType= RequestUtil.getString(request,"informType");

        try {
            if(StringUtil.isEmpty(ids)){
                return getResultDataError("bpmTaskExe.task.failure");
            }
            SysUser sysUser=(SysUser) ContextUtil.getCurrentUser();
            //取消转发/代理
            List<BpmTaskExe> exeList = bpmTaskExeService.cancelBacths(ids, sysUser, opinion, informType);
            //记录日志
            for(BpmTaskExe bpmTaskExe:exeList){
                String memo = "【" + sysUser.getFullName() + "】将转办任务【" + bpmTaskExe.getSubject()+ "】 取消";
                bpmRunLogService.addRunLog(bpmTaskExe.getRunId(),BpmRunLog.OPERATOR_TYPE_BACK, memo);
            }
            //获取取消任务失败的流程标题
            String message= MessageUtil.getMessage();
            if(message==null || message=="") {
                SysAuditThreadLocalHolder.putParamerter("success",true);
                return getResultDataSuccess("bpmTaskExe.all.cancel.success");
            }else{
                SysAuditThreadLocalHolder.putParamerter("some",true);
                return getResultDataSuccess("bpmTaskExe.some.cancel.failure",1,message);
            }

        }catch (Exception e){
            e.printStackTrace();
            logger.error(e.getMessage());
            SysAuditThreadLocalHolder.putParamerter("success",false);
            return getResultDataError("bpmTaskExe.all.cancel.failure",1,e.getMessage());
        }
    }
}
